package com.ql.dev.customwebview.library.views;

import android.annotation.TargetApi;
import android.app.Activity;
import android.content.Context;
import android.content.Intent;
import android.graphics.Bitmap;
import android.net.Uri;
import android.net.http.SslError;
import android.os.Build;
import android.os.Message;
import android.view.KeyEvent;
import android.webkit.ClientCertRequest;
import android.webkit.HttpAuthHandler;
import android.webkit.RenderProcessGoneDetail;
import android.webkit.SafeBrowsingResponse;
import android.webkit.SslErrorHandler;
import android.webkit.WebResourceError;
import android.webkit.WebResourceRequest;
import android.webkit.WebResourceResponse;
import android.webkit.WebView;
import android.webkit.WebViewClient;
import android.widget.Toast;


/**
 * Created by Quanguanzhou on  2017/3/23 0023.
 * Copyright (c) 2015, quanguanzhou83@gmail.com All Rights Reserved.
 */
public class MyWebViewClient extends WebViewClient {
    private Context mContext;
    private String openBySystem;
    private Activity activity;
    private OnWebViewClientListener onWebViewClientListener;
    public MyWebViewClient(Activity activity, String openBySystem, OnWebViewClientListener onWebViewClientListener) {
        this.mContext = activity.getApplicationContext();
        this.activity = activity;
        this.openBySystem = openBySystem;
        this.onWebViewClientListener = onWebViewClientListener;
    }

    /**
     * 在最开始的基础演示时我们用到了这个方法。从实践中我们知道，当我们没有给WebView提供WebViewClient时，
     * WebView如果要加载一个url会向ActivityManager寻求一个适合的处理者来加载该url（比如系统自带的浏览器），
     * 这通常是我们不想看到的。于是我们需要给WebView提供一个WebViewClient，并重写该方法返回true来告知WebView url的加载就在app中进行。这时便可以实现在app内访问网页。
     * @param view
     * @param url
     * @return
     */
    @Override
    public boolean shouldOverrideUrlLoading(WebView view, String url) {
        if(openBySystem.equals("1")){// 如果需要跳转到系统浏览器
            Intent intent= new Intent();
            intent.setAction("android.intent.action.VIEW");
            Uri content_url = Uri.parse(url);
            intent.setData(content_url);
            try {
                activity.startActivity(intent);
            }catch (Exception e){
                //CookieBarUtils.showMessageWithTip(activity,"未找到浏览器");
                Toast.makeText(activity,"未找到浏览器",Toast.LENGTH_SHORT).show();
            }
            return true;
        }else {
            if(onWebViewClientListener!=null){
                onWebViewClientListener.shouldOverrideUrlLoading(view,url);
            }
            return true;
        }
    }

    @Override
    public boolean shouldOverrideUrlLoading(WebView view, WebResourceRequest request) {
        if(onWebViewClientListener!=null){
            return onWebViewClientListener.shouldOverrideUrlLoading(view,request);
        }
        return super.shouldOverrideUrlLoading(view,request);
    }

    @Override
    public void onPageStarted(WebView view, String url, Bitmap favicon) {
        if(onWebViewClientListener!=null){
            onWebViewClientListener.onPageStarted(view,favicon);
        }
    }

    @Override
    public void onLoadResource(WebView view, String url) {
        if(onWebViewClientListener!=null){
            onWebViewClientListener.onLoadResource(view,url);
        }
    }

    @Override
    public void onPageCommitVisible(WebView view, String url) {
        if(onWebViewClientListener!=null){
            onWebViewClientListener.onPageCommitVisible(view,url);
        }
    }

    /**
     * 当WebView加载某个资源引发SSL错误时会回调该方法，这时WebView要么执行handler.cancel()取消加载，
     * 要么执行handler.proceed()方法继续加载（默认为cancel）。
     * 需要注意的是，这个决定可能会被保留并在将来再次遇到SSL错误时执行同样的操作。
     * @param view
     * @param handler
     * @param error
     */
    @Override
    public void onReceivedSslError(WebView view, SslErrorHandler handler, SslError error) {
        if(onWebViewClientListener!=null){
            onWebViewClientListener.onReceivedSslError(view,handler,error);
        }
    }

    /**
     * 该方法在web页面加载错误时回调，这些错误通常都是由无法与服务器正常连接引起的，最常见的就是网络问题。 这个方法有两个地方需要注意：
     *  1.这个方法只在与服务器无法正常连接时调用，类似于服务器返回错误码的那种错误（即HTTP ERROR），该方法是不会回调的，因为你已经和服务器正常连接上了（全怪官方文档(︶^︶)）；
     *  2.这个方法是新版本的onReceivedError()方法，从API23开始引进，与旧方法onReceivedError(WebView view,int errorCode,String description,String failingUrl)不同的是，
     *      新方法在页面局部加载发生错误时也会被调用（比如页面里两个子Tab或者一张图片）。这就意味着该方法的调用频率可能会更加频繁，所以我们应该在该方法里执行尽量少的操作。
     * @param view
     * @param webResourceRequest
     * @param webResourceError
     */
    @Override
    public void onReceivedError(WebView view, WebResourceRequest webResourceRequest, WebResourceError webResourceError) {
        if(onWebViewClientListener!=null){
            onWebViewClientListener.onReceivedError(view,webResourceRequest,webResourceError);
        }
    }

    /**
     * 上一个方法提到onReceivedError并不会在服务器返回错误码时被回调，那么当我们需要捕捉HTTP ERROR并进行相应操作时应该怎么办呢？API23便引入了该方法。
     * 当服务器返回一个HTTP ERROR并且它的status code>=400时，该方法便会回调。这个方法的作用域并不局限于Main Frame，
     * 任何资源的加载引发HTTP ERROR都会引起该方法的回调，所以我们也应该在该方法里执行尽量少的操作，只进行非常必要的错误处理等。
     * @param view
     * @param request
     * @param errorResponse
     */
    @TargetApi(Build.VERSION_CODES.M)
    @Override
    public void onReceivedHttpError(WebView view, WebResourceRequest request, WebResourceResponse errorResponse) {
        if(onWebViewClientListener!=null){
            onWebViewClientListener.onReceivedHttpError(view,request,errorResponse);
        }
    }

    @Override
    public WebResourceResponse shouldInterceptRequest(WebView view, WebResourceRequest request) {
        if(onWebViewClientListener!=null){
            return onWebViewClientListener.shouldInterceptRequest(view,request);
        }
        return super.shouldInterceptRequest(view,request);
    }

    @Override
    public void onPageFinished(WebView view, String url) {
        if(onWebViewClientListener!=null){
            onWebViewClientListener.onPageFinished(view,url);
        }
    }

    @Override
    public WebResourceResponse shouldInterceptRequest(WebView view, String url) {
        if(onWebViewClientListener!=null){
            return onWebViewClientListener.shouldInterceptRequest(view,url);
        }
        return super.shouldInterceptRequest(view, url);
    }

    @Override
    public void onTooManyRedirects(WebView view, Message cancelMsg, Message continueMsg) {
        super.onTooManyRedirects(view, cancelMsg, continueMsg);
    }

    @Override
    public void onReceivedError(WebView view, int errorCode, String description, String failingUrl) {
        super.onReceivedError(view, errorCode, description, failingUrl);
    }

    @Override
    public void onFormResubmission(WebView view, Message dontResend, Message resend) {
        super.onFormResubmission(view, dontResend, resend);
    }

    @Override
    public void doUpdateVisitedHistory(WebView view, String url, boolean isReload) {
        super.doUpdateVisitedHistory(view, url, isReload);
    }

    @Override
    public void onReceivedClientCertRequest(WebView view, ClientCertRequest request) {
        super.onReceivedClientCertRequest(view, request);
    }

    @Override
    public void onReceivedHttpAuthRequest(WebView view, HttpAuthHandler handler, String host, String realm) {
        super.onReceivedHttpAuthRequest(view, handler, host, realm);
    }

    @Override
    public boolean shouldOverrideKeyEvent(WebView view, KeyEvent event) {
        return super.shouldOverrideKeyEvent(view, event);
    }

    @Override
    public void onUnhandledKeyEvent(WebView view, KeyEvent event) {
        super.onUnhandledKeyEvent(view, event);
    }

    @Override
    public void onScaleChanged(WebView view, float oldScale, float newScale) {
        super.onScaleChanged(view, oldScale, newScale);
    }

    @Override
    public void onReceivedLoginRequest(WebView view, String realm, String account, String args) {
        super.onReceivedLoginRequest(view, realm, account, args);
    }

    @Override
    public boolean onRenderProcessGone(WebView view, RenderProcessGoneDetail detail) {
        return super.onRenderProcessGone(view, detail);
    }

    @Override
    public void onSafeBrowsingHit(WebView view, WebResourceRequest request, int threatType, SafeBrowsingResponse callback) {
        super.onSafeBrowsingHit(view, request, threatType, callback);
    }
}
